﻿#include "wubi_db.h"
#include <iostream>
#include <sstream>
#include <fstream>
#include <sqlite/sqlite3.h>

#include "../../log_tool.h"

/*
方案表 
CREATE TABLE IF NOT EXISTS scheme (
        id INTEGER PRIMARY KEY AUTOINCREMENT,  -- 主键，自动递增
        name TEXT NOT NULL,  -- 方案名称
        candidate_count INTEGER DEFAULT 5  // 候选词数量字段
);

码表信息
        CREATE TABLE IF NOT EXISTS code_table (
            id INTEGER PRIMARY KEY AUTOINCREMENT,
            scheme_id INTEGER NOT NULL,  -- 外键，关联方案表的id
            name TEXT NOT NULL,   -- 码表名称
            enable BOOLEAN DEFAULT 1,  -- 启用状态，默认为1（启用）
            idx INTEGER,  
            FOREIGN KEY(scheme_id) REFERENCES scheme(id) ON DELETE CASCADE
        );
        

        -- 码表数据
        CREATE TABLE IF NOT EXISTS code_table_data (
            id INTEGER PRIMARY KEY AUTOINCREMENT,
            code_table_id INTEGER NOT NULL,   -- 外键，关联码表表的id
            code TEXT NOT NULL,   -- 五笔编码
            word TEXT NOT NULL,   -- 对应的汉字
            idx INTEGER DEFAULT 0,  -- 索引，用于排序
            FOREIGN KEY(code_table_id) REFERENCES code_table(id) ON DELETE CASCADE
        );
        
        -- 用户设置使用 key -> value 存储
        key:
        default_scheme：默认方案的ID，用于快速切换

        CREATE TABLE IF NOT EXISTS user_setting (
            key TEXT PRIMARY KEY,
            value TEXT
        );
        
        CREATE INDEX IF NOT EXISTS idx_code ON code_table_data(code);
        -- 新增设置idx的触发器（添加在表创建语句后）
        CREATE TRIGGER IF NOT EXISTS set_code_table_idx AFTER INSERT ON code_table
        BEGIN
            UPDATE code_table SET idx = NEW.id WHERE id = NEW.id;
        END;

        CREATE TRIGGER IF NOT EXISTS set_code_table_data_idx AFTER INSERT ON code_table_data
        BEGIN
            UPDATE code_table_data SET idx = NEW.id WHERE id = NEW.id;
        END;
*/

WubiDb::WubiDb() : _db(nullptr) {
    
}

WubiDb::~WubiDb() {
    if(_db) {
        sqlite3_close(_db);
        _db = nullptr;
    }
}

bool WubiDb::initialize(const std::string &dbPath) {
    if(_db != nullptr){
        return true;
    }

    // 打开或创建数据库文件
    int rc = sqlite3_open(dbPath.c_str(), &_db);
    if (rc != SQLITE_OK) {
        LOG_ERROR("无法打开数据库: %s", sqlite3_errmsg(_db));
        sqlite3_close(_db);
        _db = nullptr;
        return false;
    }

    // 外键支持
    if (!executeSQL("PRAGMA foreign_keys = ON;")) {
        LOG_ERROR("启用外键约束失败");
        sqlite3_close(_db);
        _db = nullptr;
        return false;
    }

    const char* sql = R"(
        CREATE TABLE IF NOT EXISTS scheme (
            id INTEGER PRIMARY KEY AUTOINCREMENT,
            name TEXT NOT NULL,
            candidate_count INTEGER DEFAULT 5
        );
        
        CREATE TABLE IF NOT EXISTS code_table (
            id INTEGER PRIMARY KEY AUTOINCREMENT,
            scheme_id INTEGER NOT NULL,
            name TEXT NOT NULL,
            enable BOOLEAN DEFAULT 1,
            idx INTEGER DEFAULT 0,  
            FOREIGN KEY(scheme_id) REFERENCES scheme(id) ON DELETE CASCADE
        );
        
        -- 新增码表数据存储表
        CREATE TABLE IF NOT EXISTS code_table_data (
            id INTEGER PRIMARY KEY AUTOINCREMENT,
            code_table_id INTEGER NOT NULL, 
            code TEXT NOT NULL,
            word TEXT NOT NULL,
            idx INTEGER DEFAULT 0,
            FOREIGN KEY(code_table_id) REFERENCES code_table(id) ON DELETE CASCADE
        );
        
        CREATE TABLE IF NOT EXISTS user_setting (
            key TEXT PRIMARY KEY,
            value TEXT
        );
        
        CREATE INDEX IF NOT EXISTS idx_code ON code_table_data(code);

        CREATE TRIGGER IF NOT EXISTS set_code_table_idx AFTER INSERT ON code_table
        BEGIN
            UPDATE code_table SET idx = NEW.id WHERE id = NEW.id;
        END;

        CREATE TRIGGER IF NOT EXISTS set_code_table_data_idx AFTER INSERT ON code_table_data
        BEGIN
            UPDATE code_table_data SET idx = NEW.id WHERE id = NEW.id;
        END;
    )";
    
    char* errMsg = nullptr;
    rc = sqlite3_exec(_db, sql, nullptr, nullptr, &errMsg);
    if (rc != SQLITE_OK) {
        LOG_ERROR("初始化失败: %s", errMsg);
        sqlite3_free(errMsg);
        sqlite3_close(_db);
        _db = nullptr;
        return false;
    }
    return true;
}

bool WubiDb::executeSQL(const std::string& sql) {
    if (!_db) {
        LOG_ERROR("数据库未初始化"); // 替换cerr
        return false;
    }
    
    char* errMsg = nullptr;
    int rc = sqlite3_exec(_db, sql.c_str(), nullptr, nullptr, &errMsg);
    if (rc != SQLITE_OK) {
        LOG_ERROR("SQL错误: %s\n[语句] %s", errMsg, sql.c_str()); // 合并多行输出
        sqlite3_free(errMsg);
        return false;
    }
    return true;
}

MengYuIDType WubiDb::createScheme(const std::string& name) {
    if (!_db) {
        LOG_ERROR("数据库未初始化"); // 替换cerr
        return 0;
    }

    sqlite3_stmt* stmt = nullptr;
    const char* sql = "INSERT INTO scheme (name) VALUES (?);";
    
    if (sqlite3_prepare_v2(_db, sql, -1, &stmt, nullptr) != SQLITE_OK) {
        LOG_ERROR("准备语句失败: %s", sqlite3_errmsg(_db)); // 替换cerr
        return 0;
    }
    
    sqlite3_bind_text(stmt, 1, name.c_str(), -1, SQLITE_TRANSIENT);
    
    if (sqlite3_step(stmt) != SQLITE_DONE) {
        sqlite3_finalize(stmt);
        LOG_ERROR("createScheme失败: %s", sqlite3_errmsg(_db));
        return 0;
    }
    
    MengYuIDType newId = static_cast<MengYuIDType>(sqlite3_last_insert_rowid(_db));
    sqlite3_finalize(stmt);
    return newId;
}

// 获取所有方案
bool WubiDb::getAllSchemes(std::vector<WubiBaseInfoPtr> &out_schemes) {
    if (!_db) return false;
    out_schemes.clear();
    sqlite3_stmt* stmt = nullptr;
    const char* sql = "SELECT id, name FROM scheme;";
    
    if (sqlite3_prepare_v2(_db, sql, -1, &stmt, nullptr) == SQLITE_OK) {
        while (sqlite3_step(stmt) == SQLITE_ROW) {
            WubiBaseInfoPtr info;// = std::make_shared<WubiBaseInfo>();
            info->id = sqlite3_column_int(stmt, 0); 
            info->name = reinterpret_cast<const char*>(sqlite3_column_text(stmt, 1));
            out_schemes.push_back(std::move(info));
        }
    }else{
        LOG_ERROR("获取方案失败: %s", sqlite3_errmsg(_db)); // 替换cerr
        return false;
    }
    sqlite3_finalize(stmt);
    return true;
}

//方案信息获取实现
bool WubiDb::updateScheme(MengYuIDType schemeId, const std::string& name, int candidateCount) {
    if (!_db) return false;

    sqlite3_stmt* stmt = nullptr;
    const char* sql = "UPDATE scheme SET name = ?, candidate_count = ? WHERE id = ?;";
    
    if (sqlite3_prepare_v2(_db, sql, -1, &stmt, nullptr) != SQLITE_OK) {
        LOG_ERROR("准备更新语句失败: %s", sqlite3_errmsg(_db));
        return false;
    }
    
    sqlite3_bind_text(stmt, 1, name.c_str(), -1, SQLITE_TRANSIENT);
    sqlite3_bind_int(stmt, 2, candidateCount);
    sqlite3_bind_int(stmt, 3, schemeId);
    

    if (sqlite3_step(stmt) != SQLITE_DONE) {
        sqlite3_finalize(stmt);
        LOG_ERROR("updateScheme失败: %s", sqlite3_errmsg(_db));  // 修改此处
        return false;
    }
    sqlite3_finalize(stmt);
    return true;
}

bool WubiDb::getSchemeInfo(MengYuIDType schemeId, WubiBaseInfo &out_scheme) {
    if (!_db) return false;
    
    sqlite3_stmt* stmt = nullptr;
    const char* sql = "SELECT name, candidate_count FROM scheme WHERE id = ?;";  // 修改查询字段
    
    if (sqlite3_prepare_v2(_db, sql, -1, &stmt, nullptr) != SQLITE_OK) {
        LOG_ERROR("准备查询语句失败: %s", sqlite3_errmsg(_db));
        return false;
    }
    
    sqlite3_bind_int(stmt, 1, schemeId);
    
    if (sqlite3_step(stmt) == SQLITE_ROW) {
        out_scheme.id = schemeId;
        out_scheme.name = reinterpret_cast<const char*>(sqlite3_column_text(stmt, 0));
        out_scheme.candidate_count = sqlite3_column_int(stmt, 1);  // 读取候选数量
        sqlite3_finalize(stmt);
        return true;
    }
    
    sqlite3_finalize(stmt);
    LOG_ERROR("未找到方案 ID: %u", schemeId); 
    return false;
}

// 修改添加码表方法
MengYuIDType WubiDb::addCodeTable(MengYuIDType schemeId, const std::string& name) {
    if (!_db) return 0;

    sqlite3_stmt* stmt = nullptr;
    const char* sql = "INSERT INTO code_table (scheme_id, name) VALUES (?, ?);";
    
    if (sqlite3_prepare_v2(_db, sql, -1, &stmt, nullptr) != SQLITE_OK) {
        LOG_ERROR("准备语句失败: %s", sqlite3_errmsg(_db));
        return 0;
    }
    
    sqlite3_bind_int(stmt, 1, schemeId);
    sqlite3_bind_text(stmt, 2, name.c_str(), -1, SQLITE_TRANSIENT);
    
    int rc = sqlite3_step(stmt);
    
    if(rc != SQLITE_DONE){
        sqlite3_finalize(stmt);
        LOG_ERROR("运行失败: %s", sqlite3_errmsg(_db));
        return 0;
    }

    MengYuIDType codeTableId = static_cast<MengYuIDType>(sqlite3_last_insert_rowid(_db));
    sqlite3_finalize(stmt);
    return codeTableId;
}

// 获取方案的所有码表
// 修改现有查询语句，添加ORDER BY
bool WubiDb::getCodeTables(MengYuIDType schemeId,std::vector<WubiBaseInfoPtr> &out_tables) {
    if (!_db) return false;
    out_tables.clear();
    sqlite3_stmt* stmt;
    const char* sql = "SELECT id, name, enable, idx FROM code_table WHERE scheme_id = ? ORDER BY idx;";
    
    if (sqlite3_prepare_v2(_db, sql, -1, &stmt, nullptr) == SQLITE_OK) {
        sqlite3_bind_int(stmt, 1, schemeId);
        
        while (sqlite3_step(stmt) == SQLITE_ROW) {
            WubiBaseInfoPtr table;// = std::make_shared<WubiBaseInfo>();
            table->id = sqlite3_column_int(stmt, 0);
            table->name = reinterpret_cast<const char*>(sqlite3_column_text(stmt, 1));
            table->codetable_enable = sqlite3_column_int(stmt, 2);
            table->codetable_index = sqlite3_column_int(stmt, 3);
            out_tables.push_back(std::move(table));
        }
    }else{
        LOG_ERROR("获取码表失败: %s", sqlite3_errmsg(_db));
        return false;
    }
    sqlite3_finalize(stmt);
    return true;
}

// 新增数据导入方法
bool WubiDb::importCodeTableData(MengYuIDType codeTableId, 
                               const std::vector<std::pair<std::string, std::string>>& data) {
    if (!_db) return false;
    sqlite3_stmt* stmt;
    const char* sql = "INSERT INTO code_table_data (code_table_id, code, word) VALUES (?, ?, ?);";
    
    if (sqlite3_prepare_v2(_db, sql, -1, &stmt, nullptr) != SQLITE_OK) {
        return false;
    }
    
    for (const auto& item : data) {
        sqlite3_bind_int(stmt, 1, codeTableId);
        sqlite3_bind_text(stmt, 2, item.first.c_str(), -1, SQLITE_TRANSIENT);
        sqlite3_bind_text(stmt, 3, item.second.c_str(), -1, SQLITE_TRANSIENT);
        
        if (sqlite3_step(stmt) != SQLITE_DONE) {
            sqlite3_finalize(stmt);
            return false;
        }
        sqlite3_reset(stmt);
    }
    sqlite3_finalize(stmt);
    return true;
}

// 修改默认方案设置方法
bool WubiDb::setDefaultScheme(MengYuIDType schemeId) {
    if (!_db) return false;
    sqlite3_stmt* stmt;
    const char* sql = "INSERT OR REPLACE INTO user_setting (key, value) VALUES ('default_scheme', ?);";
    
    if (sqlite3_prepare_v2(_db, sql, -1, &stmt, nullptr) != SQLITE_OK) {
        LOG_ERROR("设置默认方案失败: %s", sqlite3_errmsg(_db)); 
        return false;
    }
    
    sqlite3_bind_text(stmt, 1, std::to_string(schemeId).c_str(), -1, SQLITE_TRANSIENT);

    int rc = sqlite3_step(stmt);
    if(rc != SQLITE_DONE){
        sqlite3_finalize(stmt);
        std::cerr << "setDefaultScheme: " << sqlite3_errmsg(_db) << std::endl;
        return false;
    }
    sqlite3_finalize(stmt);
    return true;
}

// 新增获取默认方案方法
MengYuIDType WubiDb::getDefaultScheme() {
    if (!_db) return 0;
    sqlite3_stmt* stmt = nullptr;
    const char* sql = "SELECT value FROM user_setting WHERE key = 'default_scheme';";
    MengYuIDType defaultId = 0;
    if (sqlite3_prepare_v2(_db, sql, -1, &stmt, nullptr) == SQLITE_OK) {
        if (sqlite3_step(stmt) == SQLITE_ROW) {
            const char* value = reinterpret_cast<const char*>(sqlite3_column_text(stmt, 0));
            defaultId = std::stoi(value);
        }
    }
    sqlite3_finalize(stmt);
    return defaultId; // 返回0表示没有默认方案
}

// 删除方案
bool WubiDb::deleteScheme(MengYuIDType schemeId) {
    if (!_db) return false;
    sqlite3_stmt* stmt;
    const char* sql = "DELETE FROM scheme WHERE id = ?;";
    
    if (sqlite3_prepare_v2(_db, sql, -1, &stmt, nullptr) != SQLITE_OK) {
        LOG_ERROR("deleteScheme error : %s", sqlite3_errmsg(_db));
        return false;
    }
    
    sqlite3_bind_int(stmt, 1, schemeId);

    int rc = sqlite3_step(stmt);
    if(rc != SQLITE_DONE){
        sqlite3_finalize(stmt);
        LOG_ERROR("deleteScheme error : %s", sqlite3_errmsg(_db));
        return false;
    }
    sqlite3_finalize(stmt);
    return true;
}

// 删除码表
bool WubiDb::removeCodeTable(MengYuIDType codeTableId) {
    if (!_db) return false;
    sqlite3_stmt* stmt;
    const char* sql = "DELETE FROM code_table WHERE id = ?;";
    
    if (sqlite3_prepare_v2(_db, sql, -1, &stmt, nullptr) != SQLITE_OK) {
        LOG_ERROR("删除码表失败: %s", sqlite3_errmsg(_db)); 
        return false;
    }
    
    sqlite3_bind_int(stmt, 1, codeTableId);
    int rc = sqlite3_step(stmt);
    if(rc != SQLITE_DONE){
        sqlite3_finalize(stmt);
        LOG_ERROR("删除码表失败: %s", sqlite3_errmsg(_db)); 
        return false;
    }
    sqlite3_finalize(stmt);
    return true;
}

// 添加单个词条（补充实现）
MengYuIDType WubiDb::addWord(MengYuIDType codeTableId, const std::string& code, const std::string& word) {
    if (!_db) return 0;
    sqlite3_stmt* stmt;
    const char* sql = "INSERT INTO code_table_data (code_table_id, code, word) VALUES (?, ?, ?);";
    
    if (sqlite3_prepare_v2(_db, sql, -1, &stmt, nullptr) != SQLITE_OK) {
        return 0;
    }
    
    sqlite3_bind_int(stmt, 1, codeTableId);
    sqlite3_bind_text(stmt, 2, code.c_str(), -1, SQLITE_TRANSIENT);
    sqlite3_bind_text(stmt, 3, word.c_str(), -1, SQLITE_TRANSIENT);
    
    int rc = sqlite3_step(stmt);
    if(rc != SQLITE_DONE){
        sqlite3_finalize(stmt);
        LOG_ERROR("addWord: %s", sqlite3_errmsg(_db)); 
        return 0;
    }
    MengYuIDType newId = static_cast<MengYuIDType>(sqlite3_last_insert_rowid(_db));
    sqlite3_finalize(stmt);
    return newId;
}

// 删除单个词条
bool WubiDb::removeWord(MengYuIDType codeTableId, const std::string& code, const std::string& word) {
    if (!_db) return false;
    sqlite3_stmt* stmt;
    const char* sql = "DELETE FROM code_table_data WHERE code_table_id = ? AND code = ? AND word = ?;";
    
    if (sqlite3_prepare_v2(_db, sql, -1, &stmt, nullptr) != SQLITE_OK) {
        return false;
    }
    
    sqlite3_bind_int(stmt, 1, codeTableId);
    sqlite3_bind_text(stmt, 2, code.c_str(), -1, SQLITE_TRANSIENT);
    sqlite3_bind_text(stmt, 3, word.c_str(), -1, SQLITE_TRANSIENT);
    
    int rc = sqlite3_step(stmt);
    if(rc != SQLITE_DONE){
        sqlite3_finalize(stmt);
        LOG_ERROR("removeWord: %s", sqlite3_errmsg(_db)); 
        return false;
    }
    sqlite3_finalize(stmt);
    return true;
}

bool WubiDb::removeWord(MengYuIDType code_id) {
    if (!_db) return false;
    
    sqlite3_stmt* stmt;
    const char* sql = "DELETE FROM code_table_data WHERE id = ?;";
    
    if (sqlite3_prepare_v2(_db, sql, -1, &stmt, nullptr) != SQLITE_OK) {
        LOG_ERROR("准备删除语句失败: %s", sqlite3_errmsg(_db));
        return false;
    }
    
    sqlite3_bind_int(stmt, 1, code_id);
    
    int rc = sqlite3_step(stmt);
    bool result = (rc == SQLITE_DONE);
    
    if(!result){
        LOG_ERROR("删除词条失败 ID=%u: %s", code_id, sqlite3_errmsg(_db));
    }
    
    sqlite3_finalize(stmt);
    return result;
}


static bool _CheckCode(std::string &code) {
    for(auto c : code) {
        if(c < 'a' || c > 'z') {
            return false;
        }
    }
    return true;
}

// 文件导入的重载方法
bool WubiDb::importCodeTableData(MengYuIDType codeTableId, const std::vector<std::string>& file_paths) {
    if (!_db) return false;
    
    // 修改事务执行结果检查
    if (!executeSQL("BEGIN IMMEDIATE TRANSACTION;")) {
        LOG_ERROR("无法开始事务");
        return false;
    }

    try {
        for (const auto& path : file_paths) {
            // 文件每行格式为 "词语 编码"
            std::ifstream file(path);
            if (!file.is_open()) {
                throw std::runtime_error("无法打开文件: " + path);
            }
            
            std::string line;
            while (std::getline(file, line)) {
                size_t pos = line.find('\t');
                if(pos == std::string::npos) {
                    continue;
                }

                std::string word = line.substr(0, pos);
                std::string code = line.substr(pos+1);
                if (code.empty() || word.empty()) {
                    continue; // 跳过空行或格式错误
                }
                if(!_CheckCode(code)) {
                    continue; // 跳过空行或格式错误
                }

                if (!addWord(codeTableId, code, word)) {
                    file.close();
                    throw std::runtime_error("插入数据失败: " + line);
                }
            }
            file.close();
        }
        // 修改为检查提交结果
        if (!executeSQL("COMMIT TRANSACTION;")) {
            throw std::runtime_error("提交事务失败");
        }
        return true;
    } catch (const std::exception& e) {
        LOG_ERROR("文件导入异常: %s", e.what());
        // 确保回滚成功
        if (!executeSQL("ROLLBACK TRANSACTION;")) {
            LOG_ERROR("回滚事务失败");
        }
        return false;
    }
}

bool WubiDb::getCodeByWord(MengYuIDType schemeId, const std::string &word, std::vector<std::string> &out_codes) {
    if (!_db) return false;
    out_codes.clear();
    
    sqlite3_stmt* stmt = nullptr;
    // 关联查询所有启用码表中的编码
    const char* sql = R"(
        SELECT DISTINCT ctd.code 
        FROM code_table_data ctd
        JOIN code_table ct ON ctd.code_table_id = ct.id 
        WHERE ct.scheme_id = ? AND ct.enable = 1 AND ctd.word = ?;
    )";

    if (sqlite3_prepare_v2(_db, sql, -1, &stmt, nullptr) != SQLITE_OK) {
        LOG_ERROR("准备编码反查语句失败: %s", sqlite3_errmsg(_db));
        return false;
    }

    sqlite3_bind_int(stmt, 1, schemeId);
    sqlite3_bind_text(stmt, 2, word.c_str(), -1, SQLITE_TRANSIENT);

    while (sqlite3_step(stmt) == SQLITE_ROW) {
        const char* code = reinterpret_cast<const char*>(sqlite3_column_text(stmt, 0));
        if (code) {
            out_codes.emplace_back(code);
        }
    }
    
    sqlite3_finalize(stmt);
    return true;
}

bool WubiDb::exportCodeTable(MengYuIDType codeTableId, const std::string &file_path) {
    if (!_db) return false;
    {
        std::ifstream file(file_path);
        if (file.good()) {
            LOG_ERROR("导出文件已存在: %s", file_path.c_str());
            return false;
        }
        file.close();
    }
    

    std::ofstream outFile(file_path, std::ios::app);
    if (!outFile.is_open()) {
        LOG_ERROR("无法创建导出文件: %s", file_path.c_str());
        return false;
    }

    sqlite3_stmt* stmt = nullptr;
    const char* sql = "SELECT code, word FROM code_table_data WHERE code_table_id = ? ORDER BY code,idx;";
    
    if (sqlite3_prepare_v2(_db, sql, -1, &stmt, nullptr) != SQLITE_OK) {
        LOG_ERROR("准备导出查询失败: %s", sqlite3_errmsg(_db));
        return false;
    }

    sqlite3_bind_int(stmt, 1, codeTableId);
    bool success = true;

    while (sqlite3_step(stmt) == SQLITE_ROW) {
        const char* code = reinterpret_cast<const char*>(sqlite3_column_text(stmt, 0));
        const char* word = reinterpret_cast<const char*>(sqlite3_column_text(stmt, 1));
        
        if (code && word) {
            outFile << word << '\t' << code << '\n';
            if (!outFile.good()) {
                LOG_ERROR("文件写入失败: %s", file_path.c_str());
                success = false;
                break;
            }
        }
    }

    sqlite3_finalize(stmt);
    outFile.close();
    return success;
}

bool WubiDb::getCodeTableDataByCode(MengYuIDType codeTableId, const std::string &code, 
                                  std::vector<WubiCodetableData> &out_data) {
    if (!_db) return false;
    out_data.clear();
    sqlite3_stmt* stmt = nullptr;
    // 添加排序条件
    const char* sql = "SELECT id, word, idx FROM code_table_data WHERE code_table_id = ? AND code = ? ORDER BY idx;";
    
    if (sqlite3_prepare_v2(_db, sql, -1, &stmt, nullptr) != SQLITE_OK) {
        LOG_ERROR("getCodeTableDataByCode error: %s", sqlite3_errmsg(_db));
        return false;
    }
    
    sqlite3_bind_int(stmt, 1, codeTableId);
    sqlite3_bind_text(stmt, 2, code.c_str(), -1, SQLITE_TRANSIENT);
    
    while (sqlite3_step(stmt) == SQLITE_ROW) {
        WubiCodetableData data;
        data.id = sqlite3_column_int(stmt, 0);
        data.word = reinterpret_cast<const char*>(sqlite3_column_text(stmt, 1));
        data.idx = sqlite3_column_int(stmt, 2); 
        out_data.push_back(std::move(data));
    }
    
    sqlite3_finalize(stmt);
    return true;
}

bool WubiDb::swapCodeTableDataOrder(MengYuIDType codeTableId, MengYuIDType code_id1, MengYuIDType code_id2) {
    if (!_db || code_id1 == code_id2) {
        LOG_ERROR("无效参数或数据库未初始化");
        return false;
    }

    // 使用事务保证原子性
    if (!executeSQL("BEGIN TRANSACTION;")) {
        LOG_ERROR("开启事务失败: %s", sqlite3_errmsg(_db));
        return false;
    }

    sqlite3_stmt* stmt = nullptr;
    // 合并查询语句同时获取两个顺序值
    const char* get_sql = "SELECT id, idx FROM code_table_data WHERE id IN (?, ?);";
    int idx1 = -1, idx2 = -1;

    if (sqlite3_prepare_v2(_db, get_sql, -1, &stmt, nullptr) == SQLITE_OK) {
        sqlite3_bind_int(stmt, 1, code_id1);
        sqlite3_bind_int(stmt, 2, code_id2);
        
        while (sqlite3_step(stmt) == SQLITE_ROW) {
            MengYuIDType id = sqlite3_column_int(stmt, 0);
            int idx = sqlite3_column_int(stmt, 1);
            
            if (id == code_id1) idx1 = idx;
            else if (id == code_id2) idx2 = idx;
        }
        sqlite3_finalize(stmt);
    }

    if (idx1 == -1 || idx2 == -1) {
        LOG_ERROR("无法找到词条顺序值 ID1=%u ID2=%u", code_id1, code_id2);
        executeSQL("ROLLBACK;");
        return false;
    }

    // 交换顺序值
    const char* update_sql = "UPDATE code_table_data SET idx = ? WHERE id = ?;";
    if (sqlite3_prepare_v2(_db, update_sql, -1, &stmt, nullptr) != SQLITE_OK) {
        LOG_ERROR("准备更新语句失败: %s", sqlite3_errmsg(_db));
        executeSQL("ROLLBACK;");
        return false;
    }

    // 更新第一个词条
    sqlite3_bind_int(stmt, 1, idx2);
    sqlite3_bind_int(stmt, 2, code_id1);
    if (sqlite3_step(stmt) != SQLITE_DONE) {
        LOG_ERROR("更新词条顺序失败 ID=%u Error: %s", code_id1, sqlite3_errmsg(_db));
        sqlite3_finalize(stmt);
        executeSQL("ROLLBACK;");
        return false;
    }
    sqlite3_reset(stmt);

    // 更新第二个词条
    sqlite3_bind_int(stmt, 1, idx1);
    sqlite3_bind_int(stmt, 2, code_id2);
    if (sqlite3_step(stmt) != SQLITE_DONE) {
        LOG_ERROR("更新词条顺序失败 ID=%u Error: %s", code_id2, sqlite3_errmsg(_db));
        sqlite3_finalize(stmt);
        executeSQL("ROLLBACK;");
        return false;
    }

    sqlite3_finalize(stmt);
    return executeSQL("COMMIT;");
}

bool WubiDb::getCodeTableData(MengYuIDType codeTableId, 
                            std::vector<std::pair<std::string, std::string>>& out_data) {
    if (!_db) return false;
    sqlite3_stmt* stmt = nullptr;
    const char* sql = "SELECT code, word FROM code_table_data WHERE code_table_id = ? ORDER BY idx;";
    
    if (sqlite3_prepare_v2(_db, sql, -1, &stmt, nullptr) != SQLITE_OK) {
        LOG_ERROR("getCodeTableData error: %s", sqlite3_errmsg(_db));
        return false;
    }
    
    sqlite3_bind_int(stmt, 1, codeTableId);
    
    while (sqlite3_step(stmt) == SQLITE_ROW) {
        const char* code = reinterpret_cast<const char*>(sqlite3_column_text(stmt, 0));
        const char* word = reinterpret_cast<const char*>(sqlite3_column_text(stmt, 1));
        if (!code || !word) { // 空值检查
            continue;
        }
        out_data.emplace_back(code, word);
    }
    
    sqlite3_finalize(stmt);
    return true;
}

bool WubiDb::swapCodeTableOrder(MengYuIDType codeTableId1, MengYuIDType codeTableId2) {
    if (!_db || codeTableId1 == codeTableId2) {
        LOG_ERROR("无效参数或数据库未初始化");  // 替换cerr
        return false;
    }

    // 使用事务保证原子性
    if (!executeSQL("BEGIN TRANSACTION;")) {
        LOG_ERROR("开启事务失败: %s", sqlite3_errmsg(_db));
        return false;
    }

    // 合并查询语句同时获取两个顺序值
    sqlite3_stmt* stmt = nullptr;
    const char* get_sql = "SELECT id, idx FROM code_table WHERE id IN (?, ?);";
    int idx1 = -1, idx2 = -1;

    if (sqlite3_prepare_v2(_db, get_sql, -1, &stmt, nullptr) == SQLITE_OK) {
        sqlite3_bind_int(stmt, 1, codeTableId1);
        sqlite3_bind_int(stmt, 2, codeTableId2);
        
        while (sqlite3_step(stmt) == SQLITE_ROW) {
            MengYuIDType id = sqlite3_column_int(stmt, 0);
            int idx = sqlite3_column_int(stmt, 1);
            
            if (id == codeTableId1) idx1 = idx;
            else if (id == codeTableId2) idx2 = idx;
        }
        sqlite3_finalize(stmt);
    }

    if (idx1 == -1 || idx2 == -1) {
        LOG_ERROR("无法找到码表顺序值 ID1=%u ID2=%u", codeTableId1, codeTableId2);
        executeSQL("ROLLBACK;");
        return false;
    }

    // 交换顺序值
    const char* update_sql = "UPDATE code_table SET idx = ? WHERE id = ?;";
    if (sqlite3_prepare_v2(_db, update_sql, -1, &stmt, nullptr) != SQLITE_OK) {
        LOG_ERROR("准备更新语句失败: %s", sqlite3_errmsg(_db));
        executeSQL("ROLLBACK;");
        return false;
    }

    // 更新第一个码表
    sqlite3_bind_int(stmt, 1, idx2);
    sqlite3_bind_int(stmt, 2, codeTableId1);
    if (sqlite3_step(stmt) != SQLITE_DONE) {
        LOG_ERROR("更新码表顺序失败 ID=%u Error: %s", codeTableId1, sqlite3_errmsg(_db));
        sqlite3_finalize(stmt);
        executeSQL("ROLLBACK;");
        return false;
    }
    sqlite3_reset(stmt);

    // 更新第二个码表
    sqlite3_bind_int(stmt, 1, idx1);
    sqlite3_bind_int(stmt, 2, codeTableId2);
    if (sqlite3_step(stmt) != SQLITE_DONE) {
        LOG_ERROR("更新码表顺序失败 ID=%u Error: %s", codeTableId2, sqlite3_errmsg(_db));
        sqlite3_finalize(stmt);
        executeSQL("ROLLBACK;");
        return false;
    }

    sqlite3_finalize(stmt);
    return executeSQL("COMMIT;");
}

bool WubiDb::setCodeTableEnable(MengYuIDType codeTableId, bool enable) {
    if (!_db) return false;
    
    sqlite3_stmt* stmt;
    const char* sql = "UPDATE code_table SET enable = ? WHERE id = ?;";
    
    if (sqlite3_prepare_v2(_db, sql, -1, &stmt, nullptr) != SQLITE_OK) {
        LOG_ERROR("准备启用状态语句失败: %s", sqlite3_errmsg(_db));
        return false;
    }
    
    sqlite3_bind_int(stmt, 1, enable ? 1 : 0);
    sqlite3_bind_int(stmt, 2, codeTableId);
    
    int rc = sqlite3_step(stmt);
    bool result = (rc == SQLITE_DONE);
    
    if(!result){
        LOG_ERROR("设置码表启用状态失败 ID=%u: %s", codeTableId, sqlite3_errmsg(_db));
    }
    
    sqlite3_finalize(stmt);
    return result;
}

